package auth

import org.springframework.security.jwt.JwtHelper
import org.springframework.security.jwt.crypto.sign.RsaSigner
import org.springframework.security.oauth2.common.OAuth2AccessToken
import org.springframework.security.oauth2.common.util.JsonParser
import org.springframework.security.oauth2.common.util.JsonParserFactory
import org.springframework.security.oauth2.provider.OAuth2Authentication
import org.springframework.security.oauth2.provider.token.store.JwtAccessTokenConverter

import java.security.KeyPair
import java.security.interfaces.RSAPrivateKey

class JwsAccessTokenConverter extends JwtAccessTokenConverter {

    private Map<String, String> headers = [:]
    private JsonParser jsonParser = JsonParserFactory.create()
    final RsaSigner signer

    JwsAccessTokenConverter(Map<String, String> headers, KeyPair keyPair) {
        super()
        super.setKeyPair(keyPair)
        this.signer = new RsaSigner(keyPair.getPrivate() as RSAPrivateKey)
        this.headers = headers
    }

    @Override
    protected String encode(OAuth2AccessToken accessToken, OAuth2Authentication authentication) {
        def user = authentication.getPrincipal() as UserEx

        Map content = [:]
        content[Constants.JWT_USER_REAL_NAME] = user.realName

        content.putAll(getAccessTokenConverter().convertAccessToken(accessToken, authentication))

        String source

        try {
            source = this.jsonParser.formatMap(content)
        } catch (Exception ex) {
            throw new IllegalStateException("Cannot convert access token to JSON", ex)
        }

        return JwtHelper.encode(source, this.signer, this.headers).getEncoded()
    }
}
